package inv.stask.logic;

import inv.stask.beans.Task;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.FileWriter;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;

public class CopyOfTaskUtil {
	
	protected String filename		= "tasks.ser";
	protected String filenameLock	= "tasks.ser.lock";
	
	public static final SimpleDateFormat sdf			= new SimpleDateFormat("dd/MM/yyyy HH:mm:ss");
	public static final SimpleDateFormat shortFormat	= new SimpleDateFormat("MMM dd");
	
	public void write(List<Task> tasks){
		synchronized (CopyOfTaskUtil.class) {
			prepareIds(tasks);
			if(lockTasks()){
				writeTasks(tasks);
				removeLock();
			}
		}
	}
	
	public List<Task> read(){
		synchronized (CopyOfTaskUtil.class) {
			if(lockTasks()){
				List<Task> list = readTasks();
				removeLock();
				
				return list;
			}
		}
		
		return null;
	}
	
	private void prepareIds(List<Task> tasks){
		int maxId	= 0;
		for(Task task: tasks){
			if(task.getId() != null)
				if(task.getId() > maxId)
					maxId = task.getId();
		}
		
		for(Task task: tasks){
			if(task.getId() == null)
				task.setId(++maxId);
		}
	}
	
	private void writeTasks(List<Task> tasks){
		FileOutputStream fos		= null;
		ObjectOutputStream oos		= null;
		
		try{
			fos		= new FileOutputStream(filename);
			oos		= new ObjectOutputStream(fos);
			
			oos.writeObject(tasks);
			
			oos.close();
		}catch(IOException io){
			System.err.println("TaskUtil.writeTasks() Fail writing tasks.");
			io.printStackTrace();
		}
	}
	
	@SuppressWarnings("unchecked")
	private List<Task> readTasks(){
		FileInputStream fis		= null;
		ObjectInputStream ois	= null;
		List<Task> list			= null;
		
		try{
			fis		= new FileInputStream(filename);
			ois		= new ObjectInputStream(fis);
			
			list	= (List<Task>) ois.readObject();
			
			ois.close();
		}catch(Exception io){
			System.err.println("TaskUtil.writeTasks() Fail reading tasks.");
			io.printStackTrace();
		}
		
		return list;
	}
	
	private boolean lockTasks(){
		File f	= new File(filenameLock);
		if(f.exists()){
			System.err.println("TaskUtil.lockTasks() File locked.");
			return false;
		}
		
		try{
			FileWriter fw	= new FileWriter(f);
			fw.write("locked at " + sdf.format(new Date()));
			fw.close();
		}catch(Exception ex){
			f.delete();
			System.err.println("TaskUtil.lockTasks() Fail locking.");
			return false;
		}
		
		return true;
	}
	
	private boolean removeLock(){
		File f	= new File(filenameLock);
		if(!f.exists()){
			System.err.println("TaskUtil.removeLock() No lock to remove.");
			return false;
		}
		
		f.delete();
		if(f.exists()){
			System.err.println("TaskUtil.removeLock() Fail to remove lock.");
			return false;
		}
		
		return true;
	}
	
}
